package com.kzn.util;


import com.kzn.entity.GlobalVar;
import com.kzn.entity.Project;
import com.kzn.entity.TimeTag;
import com.kzn.util.tmp.DHash;

import javax.imageio.ImageIO;
import java.io.*;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;

/**
 * 切割视频
 *
 * @author sorclown
 * @date 2022/2/4
 */
public class FFmpegUtil {
//    public static boolean splitVideoToJPG(String videoPath, String destDirectoryPath, String format) {
//        String suffix = format;
//        String prefix = destDirectoryPath;
//        try (FFmpegFrameGrabber frameGrabber = FFmpegFrameGrabber.createDefault(videoPath)) {
//            frameGrabber.start();
//
//            int videoLength = frameGrabber.getLengthInVideoFrames();
//            for (int i = 0; i < videoLength; i++) {
//                Frame frame = frameGrabber.grabFrame();
//                if (frame.image == null) {
//                    continue;
//                }
//                Java2DFrameConverter converter = new Java2DFrameConverter();
//                BufferedImage bfImage = converter.getBufferedImage(frame);
//
//                File outFile = new File(prefix + "/" + i + "." + suffix);
//                ImageIO.write(bfImage, suffix, outFile);
//            }
//
//        } catch (Exception e) {
//            e.printStackTrace();
//            return false;
//        }
//        return true;
//    }

//    public static boolean splitVideoByTag(String[] tag, )


    /**
     * 将视频分割为图像
     *
     * @param videoPath  视频路径
     * @param folderPath 目标文件夹
     * @param format     图片格式
     * @param fps        每秒帧数
     * @return 是否成功运行process
     */
    public static boolean splitVideoToImage(String videoPath, String folderPath, String format, int fps) {
        if (videoPath == null || format == null) {
            return false;
        }
        //创建文件夹 路径为： 源文件路径 + /image/ + 视频文件名称
        File folder = new File(folderPath);
        System.out.println(folderPath);
        boolean exists = folder.exists();
        if (!exists) {
            folder.mkdirs();
        }

        // 命令行语句
        // 形如： ffmpeg -i opening.wmv -f image2 -vf fps=1/5 -qscale:v 2 ./image/img%04d.jpg
        String command = "ffmpeg -i " + videoPath + " -f image2 -vf fps=" + fps + " -qscale:v 2 " + folderPath + "/%04d." + format;

        try {
            Process process = Runtime.getRuntime().exec(command);
            process.waitFor();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }


        return true;
    }


    public static boolean splitVideoByTag(Project project) {
        String sourcePath = GlobalVar.UPLOAD_PATH + "/" + project.getProjectName();
        String resultPath = sourcePath + "/result/";
        File[] files = new File(resultPath).listFiles();
        for (File file : files) {
            ArrayList<TimeTag> tags = new ArrayList<>();

            //读取文件中的tag
            try (FileReader reader = new FileReader(file);
                 BufferedReader br = new BufferedReader(reader)
            ) {
                String line;
                while ((line = br.readLine()) != null) {
                    // 一次读入一行数据
                    String[] arr = line.trim().split(", ");
                    TimeTag tag = new TimeTag(arr[0], Double.valueOf(arr[1]), Double.valueOf(arr[2]));
                    tags.add(tag);
                }
            } catch (IOException e) {
                e.printStackTrace();
            }

            for (TimeTag tag : tags) {
                //创建文件夹
                String downloadFolderPath = sourcePath + "/download/" + tag.getTag();
                File downloadFolder = new File(downloadFolderPath);
                if (!downloadFolder.exists()) {
                    downloadFolder.mkdirs();
                }

                //ffmpeg -ss 20.0 -t 32.2 -i [test.mp4(视频文件)] -vcodec copy -acodec copy [output.mp4(输出的视频文件)]
                String command = "ffmpeg -ss " + tag.getStart() + " -t " + tag.getEnd()
                        + " -i " + sourcePath + "/" + file.getName().split("\\.")[0] + ".mp4 -vcodec copy -acodec copy "
                        + downloadFolderPath + "/" + tag.getTag() + "_" + file.getName().split("\\.")[0] + "_output_" + tag.getStart().toString() + "_" + tag.getEnd().toString() + ".mp4";
                try {
                    Process process = Runtime.getRuntime().exec(command);
                    process.waitFor();

                } catch (IOException e) {
                    e.printStackTrace();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }

            }

        }
        return false;
    }

    /**
     * 图像去重（暂时没有用到）
     *
     * @param DirectoryPath
     * @return
     */
    public static boolean removeDuplicateImage(String DirectoryPath) {
        if (DirectoryPath == null) {
            return false;
        }
        File directory = new File(DirectoryPath);
        if (directory.isDirectory()) {

            File[] files = directory.listFiles();
            List<char[]> diffs = new LinkedList<>();
            try {
                for (File file : files) {
                    diffs.add(DHash.dHash(ImageIO.read(file)));
                }
            } catch (IOException e) {
                e.printStackTrace();
            }


            for (int i = 0; i < files.length; i++) {
                for (int j = i + 1; j < files.length; j++) {
                    if (files[i].exists()) {
                        if (DHash.diff(diffs.get(i), diffs.get(j)) > 10) {

                        }
                    } else {
                        break;
                    }
                }
            }

            return true;
        } else {
            return false;
        }

    }

//    public static void main(String[] args) {
//        String videoPath = "/Users/kezenan/Movies/《崩坏3》动画短片「阿波卡利斯如是说」.mp4";
//        String format = "jpg";
//
//
//        String path = videoPath.split("\\.")[0];
//        String[] arr = path.split("/");
//        String filename = arr[arr.length - 1];
//        String folderPath = path.substring(0, path.length() - filename.length());
//        folderPath = folderPath + "image/" + filename;
//        int fps = 4;
//
//        boolean flag = FFmpegUtil.splitVideoToImage(videoPath, folderPath, format, fps);
//        System.out.println(flag);
//
////        FFmpegUtil.removeDuplicateImage(folderPath);
//
//    }
}
